//==============================================================================
//==============================================================================
//= Classe pour sprite animé ou simple affichage
//= 04/2011 Copyfree Lentz Bruno
//==============================================================================
//==============================================================================
const C_MIDDLE = 0;
const C_TOPLEFT = 1;
const C_BOTTOMRIGHT = 2;
 
//==============================================================================
function AnimatedSprite(){
//==============================================================================
    var _this = null;
    // Pour l'animation        
    var _cptAni = 0;
    var _new = 0;
    var _last = 0;
    var _tempo = 0;                      // tempo global
    var _currentTempo = 0;               // tempo tampon au cas ou définie par animated
    var _animated = new Array();

    Sprite.call(this);    // On dérive le sprite

    // Tricks de la mort...
    _this = this;

    //=====================================================================================================
    //=====================================================================================================
    // Méthodes 'surchargées'
    //=====================================================================================================
    //=====================================================================================================
    this.set = function(source,width,height){
        _img = source;
        this.ready = true;
        this.width = width;
        this.height = height;
        this.getBorder();
    }

    this.load = function(source,width,height,setCenter){
        _img = new Image();
        _img.src = source;
        this.ready = false;
        this.width = width;
        this.height = height;
        this.getBorder();
       
        _img.onload = function(){
            _this.ready = true;
            _this.setCenter(setCenter);
            _this.getBorder();
        }
    }

    this.draw = function(context,name,taille){
        // _currentTempo : utilisé pour soit le tempo global, soit le tempo par image
        _currentTempo = _tempo;
        _new  += 1; // timer finale (pas super content mais ça ira...)
        if (taille == undefined) taille = 1;
        if (_animated[name] != undefined){     // Il faut avoir définit au moins une animation
            if (_animated[name].tempo != null) _currentTempo = _animated[name].tempo
            if (_cptAni >= _animated[name].nb) _cptAni = 0;
            
            this.width = _animated[name].width;
            this.height = _animated[name].height;
            this.widthT = this.width * taille;       // On calcul la taille
            this.heightT = this.height * taille;
            this.getBorder();
            
            context.drawImage(  _img,
                                (_animated[name].posX +_cptAni) * this.width, // Position sur la page
                                _animated[name].posY  * this.height,
                                this.width,          // Taille à découper
                                this.height,
                                this.x-this.dx,         // Position sur le context
                                this.y-this.dy,         // et repositionnage
                                this.widthT , // taille sur le context
                                this.heightT);
            
            if (_new > _currentTempo){
                _cptAni++;
                _new = 0;
            }
        } else throw "Erreur, pas d'animation pour le nom '" + name + "'!";
    }
   
    //=====================================================================================================
    //=====================================================================================================
    // Méthode d'animation 'pur'
    //=====================================================================================================
    //=====================================================================================================
    this.add = function(name,x,y,width,height,nb,tempo){
        _animated[name] = null;
        _animated[name] = new animatedSpriteObject(x,y,width,height,nb,tempo);
    }
   
    this.setTempo = function(tempo){
        _tempo = tempo;
    }
}
 
//==============================================================================
function Sprite(){
//==============================================================================
    // Le graf
    var _img = null;
    var _this = null;
   
    // L'objet est utilisable de suite
    this.ready = false;
    
    // Ces propriétées
    // position
    this.x = 0;
    this.y = 0;
    // border
    this.left = 0;
    this.right = 0;
    this.top = 0;
    this.bottom = 0;
    
    // (re)Positionnage
    this.dx = 0;
    this.dy = 0;
   
    // taille du graph à afficher
    this.width = 0;
    this.height = 0;
    this.widthT = 0;
    this.heightT = 0;
   
    // Tricks de la mort...
    _this = this;
   
    //=====================================================================================================
    //=====================================================================================================
    // Méthode d'image fixe
    //=====================================================================================================
    //=====================================================================================================
    this.set = function(source){
        _img = source;
        this.ready = true;
        this.width = _img.width;
        this.height = _img.height;
        this.getBorder();
    }
   
    this.load = function(source,setCenter,callBack){
        if (setCenter == undefined) setCenter = C_TOPLEFT;
        _img = new Image();
        _img.src = source;
       	
        _img.onload = function(){
            _this.width = this.width;
            _this.height = this.height;
            _this.setCenter(setCenter);
            _this.getBorder();
            _this.ready = true;

            if (callBack!=undefined) callBack();
        }
        this.ready = false;
    }
    
    this.draw = function(context,taille,blit){
    	var posX=0,posY=0;
    	
    	if (blit!=true){
            posX=this.left;
            posY=this.top;
    	}

    	if (taille != undefined) 
    	{
            this.widthT = this.width * taille;
            this.heightT = this.height * taille;
        } else {
            this.widthT = this.width;
            this.heightT = this.height;
        }

        context.drawImage(  _img,
                            posX,
                            posY,
                            this.widthT,
                            this.heightT
        );
    }
    //=====================================================================================================
    //=====================================================================================================
    // Méthode(s) de collision
    //=====================================================================================================
    //=====================================================================================================
    this.testCollisionXY = function(x,y){
        this.getBorder();		// D'abord s'assurer d'avoir les bonnes bordures
        var col = false;
        var xLocal,yLocal,bx,pixel;
        var buffer = document.createElement('canvas');
		   
        if (within(x,this.left,this.right)) {
            if (within(y,this.top,this.bottom)){
                xLocal = x - this.left;
                yLocal = y - this.top;

                // creer un canvas + contexte ou on blitera la region
                buffer.width = _img.width;
                buffer.height = _img.height;
                bx = buffer.getContext('2d');
                //bx.clearRect(0,0,buffer.width,buffer.height);
                bx.drawImage(_img,0,0,_img.width,_img.height);
                
                // On récupère le pixel de collision 
                pixel = bx.getImageData(xLocal,yLocal,1,1);
                // Si on as du R, du G ou du B (on se fout du A)
                if (pixel.data[0] > 0 || pixel.data[1] > 0 || pixel.data[2] > 0) col = true;
            }
        }
        buffer = null;
        return(col);
    }

    this.testCollisionDist = function(sprite){
        dist = Math.sqrt(Math.pow(this.x-sprite.x,2)+(Math.pow(this.y-sprite.y,2)));
        // Il faut prendre en compte le décalage
        if (dist < (this.widthT/2 + sprite.widthT/2))
            return true;
        else
            return false;
    }

    this.testCollisionRect = function (sprite){
        this.getBorder();		// D'abord s'assurer d'avoir les bonnes bordures
        sprite.getBorder();
        
        // Il faut prendre en compte l'origine..
        if (this.widthT > sprite.widthT){		// et on regarde qui peut être dans qui
            if (within(sprite.left,this.left,this.right) || within(sprite.right,this.left,this.right)) {
                if (this.heightT > sprite.heightT) {
                    if (within(sprite.top,this.top,this.bottom) || within(sprite.bottom,this.top,this.bottom)) return true;
                } else {
                    if (within(this.top,sprite.top,sprite.bottom) || within(this.bottom,sprite.top,sprite.bottom)) return true;
                }
            } 
        } else {
            if (within(this.left,sprite.left,sprite.right) || within(this.right,sprite.left,sprite.right)) {
                if (this.heightT > sprite.heightT) {
                    if (within(sprite.top,this.top,this.bottom) || within(sprite.bottom,this.top,this.bottom)) return true;
                } else {
                    if (within(this.top,sprite.top,sprite.bottom) || within(this.bottom,sprite.top,sprite.bottom)) return true;
                }
            } 
        }
        return false;
        //return (within(this.x-this.dx,sprite.x-sprite.dx,sprite.X-sprite.dx) || within(this.X-this.dx,sprite.x-sprite.dx,sprite.X-sprite.dx)) 
        	  //&& (within(this.y-this.dy,sprite.y-sprite.dy,sprite.Y-sprite.dy) || within(this.Y-this.dy,sprite.y-sprite.dy,sprite.Y-sprite.dy));
    }
    
    var within = function(a,b,c){
        if (a >= b && a <= c)	return true;
        else 									return false;
    }
   
    //=====================================================================================================
    //=====================================================================================================
    // Méthode de base
    //=====================================================================================================
    //=====================================================================================================
    this.getBorder = function(){
        this.left = this.x - this.dx;
        this.right = this.left + this.width;
        this.top = this.y - this.dy;
        this.bottom = this.top + this.height;
    }
   
    this.setCenter = function(/* test sur les arguments */){
        this.getBorder();
        x = 0;
        y = 0;
        
        switch (arguments.length){
            case 1 :    // C'est une constante (enfin on espère :-))
                switch(arguments[0]){
                    case C_MIDDLE :
                        x = this.width / 2;
                        y = this.height / 2;
                        break;
                    case C_BOTTOMRIGHT :
                        x = this.width;
                        y = this.height;
                        break;
                    case C_TOPLEFT :
                        x = 0;
                        y = 0;
                        break;
                }
                break;
            case 2 :
                x = argument[0];
                y = argument[1];
                break;
            default :       // Par défaut, ben c'est haut gauche
                x = 0;
                y = 0;
                break;
        }
                  
        // Au cas ou ça dépasse...
        if (x > this.width) x = this.width;
        if (y > this.height) y = this.height;
       
        this.dx = x;
        this.dy = y;
    }
}

//==================================================================================================================
//==================================================================================================================
//==================================================================================================================
//==================================================================================================================

function animatedSpriteObject(x,y,width,height,nb,tempo){
    this.posX = x;
    this.posY = y;
    this.width = width;
    this.height = height;
    this.nb = nb;
   
    if (tempo != undefined) this.tempo = tempo;
    else                    this.tempo = null;
}